package cn.gov.pbc.gd.credit.web.interceptor;

import java.util.Date;
import java.util.concurrent.Executor;
import java.util.concurrent.Executors;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

import com.alibaba.fastjson.JSON;
import com.liu.jbase.ResultVo;
import com.liu.jbase.constant.ResCode;
import com.liu.tools.DateUtil;
import com.liu.tools.LogUtil;
import com.liu.tools.NetHelper;
import com.liu.tools.StrUtil;
import com.liu.tools.WebHelper;
import com.liu.tools.conf.ConfigurerEx;

import cn.gov.pbc.gd.credit.common.constant.CodeConstant;
import cn.gov.pbc.gd.credit.common.constant.CommonConstant;
import cn.gov.pbc.gd.credit.common.constant.ConfConstant;
import cn.gov.pbc.gd.credit.common.model.UserModel;
import cn.gov.pbc.gd.credit.common.service.redis.IRedisService;
import cn.gov.pbc.gd.credit.common.util.UserUtil;
import cn.gov.pbc.gd.credit.user.service.online.IOnlineUserService;
import cn.gov.pbc.gd.credit.vo.online.OnlineUserVo;

public class WebInterceptor extends HandlerInterceptorAdapter {

	private static Logger logger = LoggerFactory.getLogger(WebInterceptor.class);
	
	@Autowired
	private IRedisService redisService;
	
	@Autowired
	private IOnlineUserService onlineUserService;
	
	private static Executor executor = Executors.newFixedThreadPool(10);
	
	@Override
	public boolean preHandle(HttpServletRequest request,
			HttpServletResponse response, Object handler) throws Exception {

		ResultVo<?> res = loginCheck(request);
		if(! ResCode.SUCCESS.equals(res.getCode())){
			
			//String uri = request.getRequestURI();
			
			request.setCharacterEncoding("UTF-8");  
	        response.setCharacterEncoding("UTF-8");  
	       
	        String uri = WebHelper.getContentPath(request);
	        
	        String accept = request.getHeader("Accept");
			if(StrUtil.isNotNull(accept) && accept.indexOf("json") != -1){
				response.setContentType("application/json;charset=UTF-8");  
				ResultVo<String> resultVo = new ResultVo<>();
				resultVo.setCode(CodeConstant.SID_CHECK_FAIL);
				resultVo.setMsg("sid 失效，请重新登录");
				resultVo.setData(uri +"/login");
				response.getOutputStream().write(JSON.toJSONString(resultVo).getBytes());
				return false;
			}
			response.setContentType("text/html;charset=UTF-8");  
	        response.getOutputStream().print("<script type=\"text/javascript\"> location.href = \""+ uri +"/login\";</script>");
			return false;
		}
		
		return super.preHandle(request, response, handler);
	}
	
	private ResultVo<?> loginCheck(HttpServletRequest request){
		
		ResultVo<?> res = new ResultVo<>();
		String sid = request.getParameter("sid");
		String ip = NetHelper.getIpAddr(request);
		UserModel userModel = UserUtil.getUserModel(sid, redisService);
		
		if(StrUtil.isNull(sid) || userModel == null){
			res.setCode(ResCode.SID_CHECK_FAIL);
			logger.error(LogUtil.msg("WebInterceptor:loginCheck", ip, "sid 不能为空"));	
			return res;
		}

		String cookie = WebHelper.getCookieValue(request, sid);
        String cook = userModel.getCookiesKey();
		
		if(! cook.equals(cookie)){
			
			res.setCode(ResCode.SID_CHECK_FAIL);
			logger.error(LogUtil.msg("WebInterceptor:loginCheck", ip, "sid与cookies不一致"));	
			return res;
		}
		
		res.setCode(ResCode.SUCCESS);
		
		executor.execute(new Runnable() {
			
			@Override
			public void run() {
				
				redisService.expire(CommonConstant.CACHE_LOGIN_PREFIX + UserUtil.getUserIdBySid(sid), ConfConstant.sidCacheTime);
				OnlineUserVo onlineUserVo = JSON.parseObject(JSON.toJSONString(userModel), OnlineUserVo.class);
				onlineUserVo.setSessionId(sid);
				onlineUserVo.setLastActiveTime(DateUtil.getCurrentFormatMill());
				logger.info(LogUtil.msg("WebInterceptor:loginCheck", "更新在线用户最后活动日期:" + JSON.toJSONString(onlineUserVo)));
				onlineUserService.update(onlineUserVo, request);			
			}
		});

		return res;
		
	}

	@Override
	public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
			ModelAndView model) throws Exception {
		
		String sid = request.getParameter("sid");
		
		Object obj = redisService.getObject(CommonConstant.CACHE_LOGIN_PREFIX + UserUtil.getUserIdBySid(sid));
		model.addObject("userModel", obj);
		model.addObject("sid", sid);
		//model.addObject("resVersion", ConfigurerEx.getProperty("res.version", DateUtil.format(new Date(), DateUtil.FORMAT_DAY)));
		String showMenu = NetHelper.getReqParams(request, "showMenu", "INDEX");
		model.addObject("showMenu", showMenu);
		
		super.postHandle(request, response, handler, model);
	}
	
	@Override
	public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
			throws Exception {
		// TODO Auto-generated method stub
		
		super.afterCompletion(request, response, handler, ex);
	}
	
}
